package com.atguigu.gulimall.order.config;

import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.amqp.support.converter.Jackson2JsonMessageConverter;
import org.springframework.amqp.support.converter.MessageConverter;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Lazy;

import javax.annotation.PostConstruct;

/**
 * @Author: fd
 * @Date 2021/8/23 15:55
 * @Description: rabbit配置类
 */
@Configuration
public class MyRabbitConfig {

	private final RabbitTemplate rabbitTemplate;

	public MyRabbitConfig(RabbitTemplate rabbitTemplate) {
		this.rabbitTemplate = rabbitTemplate;
	}

	/**
	 * 定制RabbitTemplate
	 * 1、服务收到消息就会回调
	 *      1、spring.rabbitmq.publisher-confirms: true
	 *      2、设置确认回调
	 * 2、消息正确抵达队列就会进行回调
	 *      1、spring.rabbitmq.publisher-returns: true
	 *         spring.rabbitmq.template.mandatory: true
	 *      2、设置确认回调ReturnCallback
	 *
	 * 3、消费端确认(保证每个消息都被正确消费，此时才可以broker删除这个消息)
	 *
	 * @PostConstruct MyRabbitConfig对象创建完成以后，执行这个方法
	 */
	 @PostConstruct
	 public void initRabbitTemplate() {

		/**
		 * 1、只要消息抵达Broker就ack=true
		 * correlationData：当前消息的唯一关联数据(这个是消息的唯一id)
		 * ack：消息是否成功收到
		 * cause：失败的原因
		 */
		//设置确认回调
		rabbitTemplate.setConfirmCallback((correlationData,ack,cause) -> {
			System.out.println("confirm...correlationData["+correlationData+"]==>ack:["+ack+"]==>cause:["+cause+"]");
		});


		/**
		 * 只要消息没有投递给指定的队列，就触发这个失败回调
		 * message：投递失败的消息详细信息
		 * replyCode：回复的状态码
		 * replyText：回复的文本内容
		 * exchange：当时这个消息发给哪个交换机
		 * routingKey：当时这个消息用哪个路邮键
		 */
		rabbitTemplate.setReturnCallback((message,replyCode,replyText,exchange,routingKey) -> {
			System.out.println("Fail Message["+message+"]==>replyCode["+replyCode+"]" +
					"==>replyText["+replyText+"]==>exchange["+exchange+"]==>routingKey["+routingKey+"]");
		});
	}

}
